/*
 * Copyright (C) 2014 Lucid Wolf
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */
package com.lucidhex.viewer;

import com.lucidhex.LucidWorld;
import com.lucidhex.hex.LucidCoord;
import com.lucidhex.hex.LucidHex;
import com.lucidhex.hex.LucidHexType;
import com.lucidhex.hex.LucidIndex;
import com.lucidhex.hex.PlaneCoord;
import java.awt.Point;
import java.awt.event.MouseEvent;
import java.awt.event.MouseWheelEvent;
import javax.swing.JMenu;
import javax.swing.JMenuItem;
import javax.swing.JOptionPane;
import javax.swing.JPopupMenu;
import javax.swing.event.MouseInputAdapter;

class ViewMouseListener extends MouseInputAdapter{
    private LucidWorld world;
    private ViewPortal panel;
    private int typeOfButton = -1;
    private Point start = null;
    private Point end = null;
    public ViewMouseListener(ViewPortal panel){
        this.panel = panel;
    }
    public void setErf(LucidWorld worldIn){
        world = worldIn;
    }
    @Override
    public void mouseWheelMoved(MouseWheelEvent e){
        if(!panel.isWorldLoaded()){return;}
        double rot = 1.5*e.getPreciseWheelRotation();
        if(rot < 0){
            rot = -rot;
        }else{
            rot = 1/rot;
        }
        panel.getViewOptions().zoomOnly(rot, e.getPoint());
    }
    @Override
    public void mousePressed(MouseEvent e) { 
        if(!panel.isWorldLoaded()){return;}
        if(typeOfButton != -1){return;}
        typeOfButton = e.getButton();
        start = new Point(e.getX(), e.getY());
    }		
    @Override
    public void mouseReleased(MouseEvent e){
        if(!panel.isWorldLoaded()){return;}
        end = new Point(e.getX(), e.getY());
        boolean dragged = distance(start,end) > 10.0; // catch slight drags
        if(typeOfButton == -1){return;}

        else{
            if(typeOfButton == MouseEvent.BUTTON1){
                if(dragged){
                    panel.getViewOptions().zoom(start, end);
                }else if(e.getClickCount() > 1){
                    panel.getViewOptions().reset();
                }else{
                    PlaneCoord sc = panel.getViewOptions().revTransform(end);
                    LucidIndex index = new LucidIndex(sc);
                    
                    panel.out(end.x+","+end.y+" coord = "+sc.X()+","+sc.Y()+" Index ="+index.A()+","+index.B()+","+index.C());
                    panel.setSelectedHex(world.getBoard().getHexAt(new LucidIndex(new LucidCoord(sc))));
                    
                }
            }else if(typeOfButton == MouseEvent.BUTTON2){ 
                if(dragged){
                    panel.getViewOptions().pan(start, end);
                }else{
                    panel.rotate30Deg();
                }
            }else if(typeOfButton == MouseEvent.BUTTON3){ 
                PlaneCoord sc = panel.getViewOptions().revTransform(end);
                LucidIndex ei = new LucidIndex(new LucidCoord(sc));
                LucidHex aHex = world.getBoard().getHexAt(ei);
                if(aHex == null){
                    world.getBoard().addHex(ei, LucidHexType.NULL_HEX.makeNewHex(world.getBoard()));
                    panel.repaint();
                }else{
                    JPopupMenu menu = createPopMenu(aHex, ei);
                    menu.show(e.getComponent(), e.getX(), e.getY());
                }                           
            }
        }
        typeOfButton = -1;
        start = null;
        end = null;
    }

    private double distance(Point start, Point end){
        if(start == null || end == null){return 0.0;}
        return Math.sqrt(1.0*(start.x - end.x)*(start.x - end.x)+1.0*(start.y - end.y)*(start.y - end.y));
    }

    private JPopupMenu createPopMenu(final LucidHex aHex, final LucidIndex ei) {
        JPopupMenu jppm = new JPopupMenu();
        // Hex Resets to type menu
        JMenu typeChange = new JMenu("Reset Hex To");
        // Get MenuTypes and Loop
        for(LucidHexType lht : world.getBoard().getAvailbleHexTypes()){
            JMenuItem aItem = buildPopResetHexItem(ei,lht);
            typeChange.add(aItem);
        }
        JMenuItem toDelete = new JMenuItem("Remove");
        toDelete.addActionListener(new java.awt.event.ActionListener() {
            @Override
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                world.getBoard().removeHex(ei);
                panel.repaint();
            }
        });
        jppm.add(typeChange);
        typeChange.add(toDelete);
        return jppm;
    }
    private JMenuItem buildPopResetHexItem(final LucidIndex ei, final LucidHexType aHexType){
       JMenuItem out = new JMenuItem(aHexType.getTypeName());
        out.addActionListener(new java.awt.event.ActionListener() {
            @Override
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                world.getBoard().addHex(ei, aHexType.makeNewHex(world.getBoard()));
                panel.repaint();
            }
        });
        return out;
        
    }    
}

